package com.sample.test;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

public class Solution {

    public static List<List<Integer>> permute(int[] data, int m) {

        List<List<Integer>> result = new ArrayList<>();
        List<Integer> ints = Arrays.stream(data).boxed().collect(Collectors.toList());
        dfs(result, ints, new ArrayList<>(), 0, m);
        return result;

    }

    public static void dfs(List<List<Integer>> result, List<Integer> data, List<Integer> list, int index, int m) {

        // 树的深度最大为m，终止递归
        if (index >= m) {
            // 节点为最后的结果，需要拷贝数据
            result.add(new ArrayList<>(list));
            return;
        }
        for (Integer value : data) {
            //       null
            //    /   |   \
            //   1   2    3
            // / | \
            //11  12  13
            list.add(value);
            // 递归，深度+1
            dfs(result, data, list, index + 1, m);
            // 回溯
            list.remove(value);
        }

    }

    public static void main(String[] args) {
        List<List<Integer>> lists = permute(new int[]{1, 2, 3}, 2);
    }
}

class Solution1 {
    public static void swap(List<Integer> list, int a, int b) {
        int temp = list.get(a);
        list.set(a, list.get(b));
        list.set(b, temp);

    }

    public static boolean isValid(List<Integer> list, int index, int end) {
        for (int i = index; i < end; i++) {
            if (list.get(i) == list.get(end)) {
                return false;
            }
        }
        return true;
    }

    public static void dfs(List<List<Integer>> result, List<Integer> list, int index) {
        if (index >= list.size()) {
            result.add(new ArrayList<>(list));
            return;
        }
        for (int i = index; i < list.size(); i++) {
            if (!isValid(list, index, i)) {
                continue;
            }
            swap(list, index, i);
            dfs(result, list, index + 1);
            swap(list, index, i);

        }

    }

    public static List<List<Integer>> permuteUnique(int[] num) {
        List<List<Integer>> result = new ArrayList<>();
        Arrays.sort(num);
        List<Integer> list = new ArrayList<>();
        for (int i = 0; i < num.length; i++) {
            list.add(num[i]);
        }
        dfs(result, list, 0);
        return result;
    }

}